package ink.xiaobaibai.interceptor;

import com.alibaba.fastjson.JSON;
import ink.xiaobaibai.parameterValid.BaseParameter;
import ink.xiaobaibai.parameterValid.ParameterResult;
import ink.xiaobaibai.parameterValid.ParameterValidManager;
import ink.xiaobaibai.response.ResponseFormat;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
import java.lang.annotation.Annotation;
import java.lang.reflect.Method;

/**
 * @description: 参数校验拦截器
 * @author: 小白白
 * @create: 2021-05-23
 **/

/**
 * 为 [不能使用@Validated的@Parameter参数定制的] 参数校验拦截器
 */
public class ParameterValidInterceptor implements HandlerInterceptor {

    private ParameterValidManager parameterValidManager;

    public void setParameterValidManager(ParameterValidManager parameterValidManager) {
        this.parameterValidManager = parameterValidManager;
    }

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        if (!(handler instanceof HandlerMethod)) {
            return true;
        }
        Method method = ((HandlerMethod) handler).getMethod();
        /*在方法(Controller方法)被调用前执行*/
        Annotation[][] parameterAnnotations = method.getParameterAnnotations();

        for (int i = 0; i < parameterAnnotations.length; i++) {
            for (Annotation annotation : parameterAnnotations[i]) {
                if (annotation.annotationType().getDeclaredAnnotation(BaseParameter.class) != null) {
                    ParameterResult parameterResult = this.parameterValidManager.valid(annotation, request.getParameter(method.getParameters()[i].getName()));
                    if (!parameterResult.isValid()) {
                        //未通过校验
                        this.fair(response, parameterResult.getErrorMsg());
                        return false;
                    }
                }
            }
        }
        return true;
    }

    private void fair(HttpServletResponse response, String msg) throws IOException {
        response.setCharacterEncoding("utf-8");
        response.setContentType("application/json; charset=utf-8");
        PrintWriter writer = response.getWriter();
        writer.write(JSON.toJSONString(ResponseFormat.fail(msg)));
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        /*在方法调用完后执行(调用期间出现异常,那么此方法就不会被调用)*/
    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        /*不管controller方法是否正常调用,此方法都会被执行  相当于finally*/
    }

}
